#include "Main.h"

#include <SFML\System\Clock.hpp>
#include <iostream>


#define WIN_X 800
#define WIN_Y 600
#define FRAME_RATE 30

#include "Configuration.h"

int main()
{
	Main Main;
	Main.Start();

	return 0;
}

Main::Main() :
Run(true),
Wait(0),
Mode(CallMode::high)
{
}

Main::~Main()
{
	//Cfg.Save();
}

void Main::Start()
{
	Window.create(sf::VideoMode(WIN_X, WIN_Y), "NeurEvo", sf::Style::Default);
	Window.setFramerateLimit(FRAME_RATE);

	Context.Create();

	glCullFace(GL_BACK);

	unsigned long long int Frame = 0;

	sf::Clock Clock;
	Clock.restart();
	int Time = (int)Clock.getElapsedTime().asSeconds();
	int UpdateCountLast = 0;

	while (Run)
	{
		Frame++;

		const int NewTime = (int)Clock.getElapsedTime().asSeconds();

		if (Time != NewTime)
		{
			Time = NewTime;

			//system("cls");
			/*
			std::cout << "SECONDS:		" << Time << std::endl;
			std::cout << "UPDATES:		" << Context.UpdateCount << std::endl;
			std::cout << "UPS:			" << (Context.UpdateCount - UpdateCountLast) << std::endl;
			std::cout << std::endl;
			std::cout << "CREATURES:		" << Context.Creatures.GetCount() << std::endl;
			std::cout << std::endl;
			std::cout << "========================" <<std::endl;
			std::cout << std::endl;
			UpdateCountLast = Context.UpdateCount;*/
		}
		

		PollEvents();
		Draw();

		switch (Mode)
		{
		case CallMode::veryslow:
			if ((Frame % (FRAME_RATE)) == 1)
				Context.Update();
			break;

		case CallMode::slow:
			if ((Frame % (FRAME_RATE / 15)) == 1)
				Context.Update();
			break;

		case CallMode::high:
			Context.Update();
			break;

		case CallMode::veryhigh:
			Context.Update();
			Context.Update();
			Context.Update();
			Context.Update();
			Context.Update();
			Context.Update();
			Context.Update();
			Context.Update();
			Context.Update();
			Context.Update();
			break;
		}		
	}
};

void Main::PollEvents()
{
	sf::Event Event;
	while (Window.pollEvent(Event))
	{
		if (Event.type == sf::Event::Closed)
		{
			Run = false;
		}
		else if (Event.type == sf::Event::KeyPressed)
		{
			if (Event.key.code == sf::Keyboard::Space)
				Context.Create();

			else if (Event.key.code == sf::Keyboard::Return)
				Context.AddCreatures();

			else if (Event.key.code == sf::Keyboard::Num1)
				Mode = (CallMode::veryslow);

			else if (Event.key.code == sf::Keyboard::Num2)
				Mode = (CallMode::slow);

			else if (Event.key.code == sf::Keyboard::Num3)
				Mode = (CallMode::high);

			else if (Event.key.code == sf::Keyboard::Num4)
				Mode = (CallMode::veryhigh);

			else if (Event.key.code == sf::Keyboard::I)
				Context.ImportConfig();

			else if (Event.key.code == sf::Keyboard::E)
				Context.ExportConfig();

			else if (Event.key.code == sf::Keyboard::S)
				Context.Save();

			else if (Event.key.code == sf::Keyboard::L)
			{
				Context.Load();
			}


		}
		else if (Event.type == sf::Event::MouseButtonPressed)
		{
			/*
			if (Event.mouseButton.button == sf::Mouse::Left)
			{
				double x = (double)sf::Mouse::getPosition(WindowHabitat).x;
				double y = (double)sf::Mouse::getPosition(WindowHabitat).y;
				x = x / (double)WindowHabitat.getSize().x;
				y = y / (double)WindowHabitat.getSize().y;
				x = x * (double)HABITAT_SIZE_X;
				y = y * (double)HABITAT_SIZE_Y;
				
			}
			else if (Event.mouseButton.button == sf::Mouse::Right)
			{
				double x = (double)sf::Mouse::getPosition(WindowHabitat).x;
				double y = (double)sf::Mouse::getPosition(WindowHabitat).y;
				x = x / (double)WindowHabitat.getSize().x;
				y = y / (double)WindowHabitat.getSize().y;
				x = x * (double)HABITAT_SIZE_X;
				y = y * (double)HABITAT_SIZE_Y;
				
			}*/

		}
		/*
		else if (Event.type == sf::Event::MouseMoved)
		{
			double x = (double)sf::Mouse::getPosition(WindowHabitat).x;
			double y = (double)sf::Mouse::getPosition(WindowHabitat).y;
			x = x / (double)WindowHabitat.getSize().x;
			y = y / (double)WindowHabitat.getSize().y;
			x = x * (double)HABITAT_SIZE_X;
			y = y * (double)HABITAT_SIZE_Y;

			if (sf::Mouse::isButtonPressed(sf::Mouse::Left) == true)
			{
				Context.Select((int)x, (int)y);
			}

			if (sf::Mouse::isButtonPressed(sf::Mouse::Right) == true)
			{
				Context.Kill((int)x, (int)y);
			}

			Wait = FRAME_WAIT;
		}*/
	}

	if (sf::Keyboard::isKeyPressed(sf::Keyboard::Key::PageUp) == true)
		Context.Cam.ZoomIn();

	if (sf::Keyboard::isKeyPressed(sf::Keyboard::Key::PageDown) == true)
		Context.Cam.ZoomOut();

	if (sf::Keyboard::isKeyPressed(sf::Keyboard::Key::Up) == true)
		Context.Cam.Up();

	if (sf::Keyboard::isKeyPressed(sf::Keyboard::Key::Down) == true)
		Context.Cam.Down();

	if (sf::Keyboard::isKeyPressed(sf::Keyboard::Key::Left) == true)
		Context.Cam.Left();

	if (sf::Keyboard::isKeyPressed(sf::Keyboard::Key::Right) == true)
		Context.Cam.Right();


}

void Main::SetGl()
{
	//obsolet
}

void Main::Draw()
{
	//fenster 1

	const float Ratio = (float)Window.getSize().x / (float)Window.getSize().y;
	int X = Window.getSize().x;
	int Y = Window.getSize().y;

	Window.setActive(true);

	glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);

	glLoadIdentity();
	glViewport(0, 0, X, Y);

	glScalef(
		(Context.Cam.Zoom * 2.f / (float)X),
		(Context.Cam.Zoom *-2.f / (float)Y),
		1.f);

	glTranslatef(-1.f + Context.Cam.PosX, 1.f + Context.Cam.PosY, 0.f);


	Context.DrawHabitat();


	glLoadIdentity();
	glViewport(0, 0, Y / 5, Y / 5);

	glScalef(1.f, -1.f, 1.f);


	//glTranslatef(-1.f, 1.f, 0.f);
	glPointSize((float)(WIN_Y / 50));
	glEnable(GL_POINT_SMOOTH);

	Context.DrawSelected();


	//anzeigen
	Window.display();
}